package reference

import (
	"api-gateway-core/common"
	"api-gateway-core/mapping"
	"dubbo.apache.org/dubbo-go/v3/config"
	"dubbo.apache.org/dubbo-go/v3/config/generic"
	_ "dubbo.apache.org/dubbo-go/v3/imports"
	"errors"
	"fmt"
)

type ReferenceRegistry struct {
	configuration *common.Configuration
	//泛化调用服务存储
	knownReference map[string]*generic.GenericService
}

func NewReferenceRegistry(configuration *common.Configuration) *ReferenceRegistry {
	return &ReferenceRegistry{configuration: configuration, knownReference: map[string]*generic.GenericService{}}
}

func (this *ReferenceRegistry) GetReference(statement *mapping.HttpStatement) (*generic.GenericService, error) {
	key := statement.URI + "-" + string(statement.HttpCommandType)
	if genericService, ok := this.knownReference[key]; ok {
		return genericService, nil
	}
	return nil, errors.New("Uri " + key + " is not known to the MapperRegistry.")
}

func (this *ReferenceRegistry) AddGenericReference(statement *mapping.HttpStatement) error {
	key := statement.URI + "-" + string(statement.HttpCommandType)
	if _, ok := this.knownReference[key]; ok {
		return errors.New("Uri " + key + " is already known to the MapperRegistry.")
	}
	this.knownReference[key] = NewGenericService(this.configuration, statement)
	this.configuration.AddStatement(statement)
	return nil
}

// 创建泛化调用服务
func NewGenericService(configuration *common.Configuration, statement *mapping.HttpStatement) *generic.GenericService {
	interfaceName := statement.InterfaceName
	applicationName := statement.Application
	//
	referenceConfig := configuration.ReferenceConfigMap[interfaceName]
	rootConfig := config.NewRootConfigBuilder().
		SetRegistries(configuration.RegistryConfigMap).Build()
	_ = rootConfig.Init()
	if err := referenceConfig.Init(rootConfig); err != nil {
		fmt.Println("初始化失败"+"----------------", err)
	}
	referenceConfig.GenericLoad(applicationName)
	return referenceConfig.GetRPCService().(*generic.GenericService)
}
